//
//  vhECGPath.m
//  vhECGTools
//
//  Created by jia yu on 2021/11/19.
//

#import "vhECGPath.h"

@implementation vhECGPath
#pragma mark - 12 x 1
+(CGMutablePathRef)build12x1Path:(NSArray <NSArray <NSNumber *>*>*)ecgsArray zeroX:(float)start_x pointPerPoint:(float)seekPerPoint zeroY:(float)start_y rateY:(float)y_rate lineSpace:(float)perlineSpace pix:(float)pixPermm{
    NSArray *array = @[@YES,@YES,@YES,
                       @YES,@YES,@YES,
                       @YES,@YES,@YES,
                       @YES,@YES,@YES];
    return [vhECGPath buildCustomPath:ecgsArray zeroX:start_x pointPerPoint:seekPerPoint zeroY:start_y rateY:y_rate lineSpace:perlineSpace pix:pixPermm customLeads:array];
}

+(void)draw12x1LeadName:(NSDictionary *)standardAtt startX:(float)start_x startY:(float)start_y lineSpace:(float)perlineSpace pixPermm:(float)pixPermm{
    NSArray *array = @[@YES,@YES,@YES,
                       @YES,@YES,@YES,
                       @YES,@YES,@YES,
                       @YES,@YES,@YES];
    [vhECGPath drawCustomLeadName:standardAtt startX:start_x startY:start_y lineSpace:perlineSpace pixPermm:pixPermm customLeads:array];
    return;
}

+(CGMutablePathRef)build12x1STPath:(NSArray <NSArray <NSNumber *>*>*)stsArray uvs:(NSArray <NSNumber *>*)uvsArray slopes:(NSArray <NSNumber *>*)slopesArray posZ:(short)Z posJ:(short)J posJms:(NSInteger)jmsIndex zeroX:(float)start_x zeroY:(float)start_y rateY:(float)y_rate pointPerPoint:(float)seekPerPoint lineSpace:(float)perLineSpace pixPermm:(float)pixPermm{
    float middleY = start_y + perLineSpace * 0.66f;
    CGMutablePathRef path = CGPathCreateMutable();
    for (int i=0;i<12;i++){
        NSArray *templatesArray = [stsArray objectAtIndex:i];
//        NSNumber *uv = [uvsArray objectAtIndex:i];
//        NSNumber *slope = [slopesArray objectAtIndex:i];
        BOOL isPenDown = NO;
        float currentX = start_x;
        for (NSNumber *num in templatesArray){
            float y = middleY - pixPermm * y_rate * [num floatValue]/1000.f;
            if (isPenDown){
                CGPathAddLineToPoint(path, NULL, currentX, y);
            }else{
                isPenDown = YES;
                CGPathMoveToPoint(path, NULL, currentX, y);
            }
            currentX += seekPerPoint;
        }
        //draw Z
        CGPathMoveToPoint(path, NULL, start_x + Z * seekPerPoint, middleY - 2.f * pixPermm);
        CGPathAddLineToPoint(path, NULL, start_x + Z * seekPerPoint, middleY + 2.f * pixPermm);
        //draw J
        CGPathMoveToPoint(path, NULL, start_x + J * seekPerPoint, middleY - 2.f * pixPermm);
        CGPathAddLineToPoint(path, NULL, start_x + J * seekPerPoint, middleY + 2.f * pixPermm);
        //draw Jms
        CGPathMoveToPoint(path, NULL, start_x + jmsIndex * seekPerPoint, middleY - 2.f * pixPermm);
        CGPathAddLineToPoint(path, NULL, start_x + jmsIndex * seekPerPoint, middleY + 2.f * pixPermm);

        CGPathMoveToPoint(path, NULL, -1.f, -1.f);
        CGPathCloseSubpath(path);
        middleY += perLineSpace;
    }
    return path;
}

+(void)draw12x1STValue:(NSDictionary *)fontAtt
              unitFont:(NSDictionary *)unitFontAtt
                   uvs:(NSArray <NSNumber *>*)uvsArray
               uvsUnit:(UISettingSTUnit)unit
                slopes:(NSArray <NSNumber *>*)slopesArray
                 zeroX:(float)start_x
                 zeroY:(float)start_y
                 width:(float)width
             lineSpace:(float)lineSpace{
    float currentY = start_y;
    for (int i=0;i<uvsArray.count;i++){
        NSNumber *uv = [uvsArray objectAtIndex:i];
        NSNumber *slope = [slopesArray objectAtIndex:i];
        NSString *uvStr = @"";
        if (UISettingSTUnit_MM == unit){
            uvStr = [NSString stringWithFormat:@"%.1f", 10.f * [uv floatValue]/1000.f];
        }else{
            uvStr = [NSString stringWithFormat:@"%.2f", [uv floatValue]/1000.f];
        }
        NSString *slopeStr = [NSString stringWithFormat:@"%.2f", [slope floatValue]];
        [uvStr drawInRect:CGRectMake(start_x, currentY+10.f, width - 5.2f * PixPermm300DPI, lineSpace/2.f) withAttributes:fontAtt];
        NSString *uvUnit = @"";
        if (UISettingSTUnit_MM == unit){
            uvUnit = @"mm";
        }else{
            uvUnit = @"mV";
        }
        [uvUnit drawInRect:CGRectMake(start_x + width - 4.5f * PixPermm300DPI, currentY + 10.f, 4.5f * PixPermm300DPI, lineSpace/2.f) withAttributes:unitFontAtt];
        [slopeStr drawInRect:CGRectMake(start_x, currentY+40.f, width - 5.2f * PixPermm300DPI, lineSpace/2.f) withAttributes:fontAtt];
        [@"mV/s" drawInRect:CGRectMake(start_x + width - 4.5f * PixPermm300DPI, currentY + 40.f, 4.5f * PixPermm300DPI, lineSpace/2.f) withAttributes:unitFontAtt];
        currentY += lineSpace;
    }
    return;
}



#pragma mark - 3x4
+(CGMutablePathRef)build3x4Path:(NSArray <NSArray <NSNumber *>*>*)ecgsArray fullLead:(ECGLead)extLead ecgFromIndex:(int)fromIndex zeroX:(float)start_x pointPerPoint:(float)seekPerPoint zeroY:(float)start_y rateY:(float)y_rate lineSpace:(float)perlineSpace pix:(float)pixPermm{
    if (nil == ecgsArray || 12 != ecgsArray.count){
        return nil;
    }
    CGMutablePathRef path = CGPathCreateMutable();
    float currentX = 0.f;
    NSInteger indexFrom = fromIndex;
    //ECG结束位置留白 5mm
    NSInteger spacePointsNumber = 5.f * pixPermm / seekPerPoint;
    NSInteger indexLen = ecgsArray.firstObject.count/4 - spacePointsNumber;
    NSInteger indexTo = indexFrom + indexLen;
    for (int i=0;i<12;i++){
        float middle = start_y + (i%3 + 0.66f) * perlineSpace;
        currentX = start_x + (seekPerPoint * (indexLen + spacePointsNumber)) * (i/3);
        NSArray *leadECGsArray = [ecgsArray objectAtIndex:i];
        
        //前3个导联有定标
        if (i < 3){
            CGPathMoveToPoint(path, NULL, currentX, middle);
            currentX += 1.5f * pixPermm;
            CGPathAddLineToPoint(path, NULL, currentX, middle);
            CGPathAddLineToPoint(path, NULL, currentX, middle - y_rate * pixPermm);
            currentX += 2.f * pixPermm;
            CGPathAddLineToPoint(path, NULL, currentX, middle - y_rate * pixPermm);
            CGPathAddLineToPoint(path, NULL, currentX, middle);
            currentX += 1.5f * pixPermm;
            CGPathAddLineToPoint(path, NULL, currentX, middle);
            CGPathMoveToPoint(path, NULL, -1.f, -1.f);
            CGPathCloseSubpath(path);
        }else{
            //后面的导联跳过定标宽度
            currentX += 5.f * pixPermm;
            
            //画小竖线 取消画小竖线 Jan 20 2022
//            CGPathMoveToPoint(path, NULL, currentX, middle);
//            CGPathAddLineToPoint(path, NULL, currentX, middle - 10.f * pixPermm);
//            CGPathMoveToPoint(path, NULL, -1.f, -1.f);
//            CGPathCloseSubpath(path);
        }
        
        //ECG line start
        BOOL isPenDown = NO;
        for (NSInteger index = indexFrom;index<indexTo;index++){
            NSNumber *num = [leadECGsArray objectAtIndex:index];
            float y = middle - pixPermm * y_rate * [num floatValue]/1000.f;
            if (isPenDown){
                CGPathAddLineToPoint(path, NULL, currentX, y);
            }else{
                CGPathMoveToPoint(path, NULL, currentX, y);
                isPenDown = YES;
            }
            currentX += seekPerPoint;
        }
        CGPathMoveToPoint(path, NULL, -1.f, -1.f);
        CGPathCloseSubpath(path);
    }
    
    //draw ext lead
    float middle = start_y + 3.66f * perlineSpace;
    currentX = start_x;
    CGPathMoveToPoint(path, NULL, currentX, middle);
    currentX += 1.5f * pixPermm;
    CGPathAddLineToPoint(path, NULL, currentX, middle);
    CGPathAddLineToPoint(path, NULL, currentX, middle - y_rate * pixPermm);
    currentX += 2.f * pixPermm;
    CGPathAddLineToPoint(path, NULL, currentX, middle - y_rate * pixPermm);
    CGPathAddLineToPoint(path, NULL, currentX, middle);
    currentX += 1.5f * pixPermm;
    CGPathAddLineToPoint(path, NULL, currentX, middle);
    CGPathMoveToPoint(path, NULL, -1.f, -1.f);
    CGPathCloseSubpath(path);
    
    BOOL isPenDown = NO;
    for (NSNumber *num in [ecgsArray objectAtIndex:extLead]){
        float y = middle - pixPermm * y_rate * [num floatValue]/1000.f;
        if (isPenDown){
            CGPathAddLineToPoint(path, NULL, currentX, y);
        }else{
            CGPathMoveToPoint(path, NULL, currentX, y);
            isPenDown = YES;
        }
        currentX += seekPerPoint;
    }
    CGPathMoveToPoint(path, NULL, -1.f, -1.f);
    CGPathCloseSubpath(path);

    return path;
}

+(void)draw3x4LeadName:(NSDictionary *)standardAtt fullLead:(ECGLead)extLead zeroX:(float)start_x ecgWidth:(float)ecgWidth zeroY:(float)start_y lineSpace:(float)perlineSpace pix:(float)pixPermm{
    CGRect rect = CGRectZero;
    NSString *leadName = @"";
    //最左侧有定标的导联名
    float middle = start_y + perlineSpace * 0.66f;
    for (int i=0;i<4;i++){
        rect = CGRectMake(start_x, middle, 5.f * pixPermm, 40.f);
        if (3 == i){
            leadName = [vhECGTools leadName:extLead];
        }else{
            leadName = [vhECGTools leadName:i];
        }
        [leadName drawInRect:rect withAttributes:standardAtt];
        middle += perlineSpace;
    }
    
    //画后面3列的定标名
    for (int i=3;i<12;i++){
        float currentX = start_x + 5.f * pixPermm + ecgWidth * (i/3);
        middle = start_y + (i%3 + 0.66f) * perlineSpace - 5.f * pixPermm;
        rect = CGRectMake(currentX, middle, 5.f * pixPermm, 40.f);
        leadName = [vhECGTools leadName:i];
        [leadName drawInRect:rect withAttributes:standardAtt];
    }
    return;
}

+(CGMutablePathRef)build3x4ContinuncePath:(NSArray <NSArray <NSNumber *>*>*)ecgsArray fullLead:(ECGLead)extLead zeroX:(float)start_x pointPerPoint:(float)seekPerPoint zeroY:(float)start_y rateY:(float)y_rate lineSpace:(float)perlineSpace pix:(float)pixPermm;{
    CGMutablePathRef path = CGPathCreateMutable();
    float currentX = 0.f;
    NSInteger indexFrom = 0;
    NSInteger indexLen = ecgsArray.firstObject.count/4;
    NSInteger indexTo = indexFrom + indexLen;

    for (int i=0;i<12;i++){
        float middle = start_y + (i%3 + 0.66) * perlineSpace;
        currentX = start_x + (seekPerPoint * indexLen) * (i/3);
        NSArray *leadECGsArray = [ecgsArray objectAtIndex:i];
        
        //前3个导联有定标
        if (i < 3){
            CGPathMoveToPoint(path, NULL, currentX, middle);
            currentX += 1.5f * pixPermm;
            CGPathAddLineToPoint(path, NULL, currentX, middle);
            CGPathAddLineToPoint(path, NULL, currentX, middle - y_rate * pixPermm);
            currentX += 2.f * pixPermm;
            CGPathAddLineToPoint(path, NULL, currentX, middle - y_rate * pixPermm);
            CGPathAddLineToPoint(path, NULL, currentX, middle);
            currentX += 1.5f * pixPermm;
            CGPathAddLineToPoint(path, NULL, currentX, middle);
            CGPathMoveToPoint(path, NULL, -1.f, -1.f);
            CGPathCloseSubpath(path);
        }else{
            //后面的导联跳过定标宽度
            currentX += 5.f * pixPermm;
            //画小竖线
            CGPathMoveToPoint(path, NULL, currentX, middle);
            CGPathAddLineToPoint(path, NULL, currentX, middle - 10.f * pixPermm);
            CGPathMoveToPoint(path, NULL, -1.f, -1.f);
            CGPathCloseSubpath(path);
        }
        
        //ECG line start
        BOOL isPenDown = NO;
        indexFrom = indexLen * (i/3);
        indexTo = indexFrom + indexLen;

        // disableDrawIndex 大于这个数值的ECG点，只占位不划，效果就是空开一段距离。
        NSInteger disableDrawIndex = indexTo - 0.f * pixPermm / seekPerPoint;

        for (NSInteger index = indexFrom;index<indexTo;index++){
            NSNumber *num = [leadECGsArray objectAtIndex:index];
            float y = middle - pixPermm * y_rate * [num floatValue]/1000.f;
            if (isPenDown && index < disableDrawIndex){
                CGPathAddLineToPoint(path, NULL, currentX, y);
            }else{
                CGPathMoveToPoint(path, NULL, currentX, y);
                isPenDown = YES;
            }
            currentX += seekPerPoint;
        }
        CGPathMoveToPoint(path, NULL, -1.f, -1.f);
        CGPathCloseSubpath(path);
    }
    
    //draw ext lead
    float middle = start_y + 3.66f * perlineSpace;
    currentX = start_x;
    CGPathMoveToPoint(path, NULL, currentX, middle);
    currentX += 1.5f * pixPermm;
    CGPathAddLineToPoint(path, NULL, currentX, middle);
    CGPathAddLineToPoint(path, NULL, currentX, middle - y_rate * pixPermm);
    currentX += 2.f * pixPermm;
    CGPathAddLineToPoint(path, NULL, currentX, middle - y_rate * pixPermm);
    CGPathAddLineToPoint(path, NULL, currentX, middle);
    currentX += 1.5f * pixPermm;
    CGPathAddLineToPoint(path, NULL, currentX, middle);
    CGPathMoveToPoint(path, NULL, -1.f, -1.f);
    CGPathCloseSubpath(path);
    
    BOOL isPenDown = NO;
    for (NSNumber *num in [ecgsArray objectAtIndex:extLead]){
        float y = middle - pixPermm * y_rate * [num floatValue]/1000.f;
        if (isPenDown){
            CGPathAddLineToPoint(path, NULL, currentX, y);
        }else{
            CGPathMoveToPoint(path, NULL, currentX, y);
            isPenDown = YES;
        }
        currentX += seekPerPoint;
    }
    CGPathMoveToPoint(path, NULL, -1.f, -1.f);
    CGPathCloseSubpath(path);
    return path;
}

#pragma mark - 6x2
+(CGMutablePathRef)build6x2Path:(NSArray <NSArray <NSNumber *>*>*)ecgsArray fullLead:(ECGLead)extLead ecgFromIndex:(int)fromIndex zeroX:(float)start_x pointPerPoint:(float)seekPerPoint zeroY:(float)start_y rateY:(float)y_rate lineSpace:(float)perlineSpace pix:(float)pixPermm{
    CGMutablePathRef path = CGPathCreateMutable();
    float currentX = 0.f;
    NSInteger indexFrom = fromIndex;
    
    NSInteger spacePointsNumber = 5.f * pixPermm / seekPerPoint;
    NSInteger indexLen = ecgsArray.firstObject.count/2 - spacePointsNumber;
    NSInteger indexTo = indexFrom + indexLen;
    for (int i=0;i<12;i++){
        float middle = start_y + (i%6 + 0.66f) * perlineSpace;
        currentX = start_x + (seekPerPoint * (indexLen + spacePointsNumber)) * (i/6);
        NSArray *leadECGsArray = [ecgsArray objectAtIndex:i];

        //前3个导联有定标
        if (i < 6){
            CGPathMoveToPoint(path, NULL, currentX, middle);
            currentX += 1.5f * pixPermm;
            CGPathAddLineToPoint(path, NULL, currentX, middle);
            CGPathAddLineToPoint(path, NULL, currentX, middle - y_rate * pixPermm);
            currentX += 2.f * pixPermm;
            CGPathAddLineToPoint(path, NULL, currentX, middle - y_rate * pixPermm);
            CGPathAddLineToPoint(path, NULL, currentX, middle);
            currentX += 1.5f * pixPermm;
            CGPathAddLineToPoint(path, NULL, currentX, middle);
            CGPathMoveToPoint(path, NULL, -1.f, -1.f);
            CGPathCloseSubpath(path);
        }else{
            //后面的导联跳过定标宽度
            currentX += 5.f * pixPermm;
            //画小竖线， 取消画小竖线 Jan 20 2022
//            CGPathMoveToPoint(path, NULL, currentX, middle);
//            CGPathAddLineToPoint(path, NULL, currentX, middle - 10.f * pixPermm);
//            CGPathMoveToPoint(path, NULL, -1.f, -1.f);
//            CGPathCloseSubpath(path);
        }

        //ECG line start
        BOOL isPenDown = NO;
        for (NSInteger index = indexFrom;index<indexTo;index++){
            NSNumber *num = [leadECGsArray objectAtIndex:index];
            float y = middle - pixPermm * y_rate * [num floatValue]/1000.f;
            if (isPenDown){
                CGPathAddLineToPoint(path, NULL, currentX, y);
            }else{
                CGPathMoveToPoint(path, NULL, currentX, y);
                isPenDown = YES;
            }
            currentX += seekPerPoint;
        }
        CGPathMoveToPoint(path, NULL, -1.f, -1.f);
        CGPathCloseSubpath(path);
    }

    //draw ext lead
    float middle = start_y + 6.66f * perlineSpace;
    currentX = start_x;
    CGPathMoveToPoint(path, NULL, currentX, middle);
    currentX += 1.5f * pixPermm;
    CGPathAddLineToPoint(path, NULL, currentX, middle);
    CGPathAddLineToPoint(path, NULL, currentX, middle - y_rate * pixPermm);
    currentX += 2.f * pixPermm;
    CGPathAddLineToPoint(path, NULL, currentX, middle - y_rate * pixPermm);
    CGPathAddLineToPoint(path, NULL, currentX, middle);
    currentX += 1.5f * pixPermm;
    CGPathAddLineToPoint(path, NULL, currentX, middle);
    CGPathMoveToPoint(path, NULL, -1.f, -1.f);
    CGPathCloseSubpath(path);

    BOOL isPenDown = NO;
    for (NSNumber *num in [ecgsArray objectAtIndex:extLead]){
        float y = middle - pixPermm * y_rate * [num floatValue]/1000.f;
        if (isPenDown){
            CGPathAddLineToPoint(path, NULL, currentX, y);
        }else{
            CGPathMoveToPoint(path, NULL, currentX, y);
            isPenDown = YES;
        }
        currentX += seekPerPoint;
    }
    CGPathMoveToPoint(path, NULL, -1.f, -1.f);
    CGPathCloseSubpath(path);
    return path;
}

+(void)draw6x2LeadName:(NSDictionary *)standardAtt fullLead:(ECGLead)extLead zeroX:(float)start_x ecgWidth:(float)ecgWidth zeroY:(float)start_y lineSpace:(float)perlineSpace pix:(float)pixPermm{
    CGRect rect = CGRectZero;
    NSString *leadName = @"";
    //最左侧有定标的导联名
    float middle = start_y + perlineSpace * 0.66f;
    for (int i=0;i<7;i++){
        rect = CGRectMake(start_x, middle, 5.f * pixPermm, 40.f);
        if (6 == i){
            leadName = [vhECGTools leadName:extLead];
        }else{
            leadName = [vhECGTools leadName:i];
        }
        [leadName drawInRect:rect withAttributes:standardAtt];
        middle += perlineSpace;
    }
    
    //画后面列的定标名
    for (int i=6;i<12;i++){
        float currentX = start_x + 5.f * pixPermm + ecgWidth;
        middle = start_y + (i%6 + 1) * perlineSpace - 5.f * pixPermm;
        rect = CGRectMake(currentX, middle, 5.f * pixPermm, 40.f);
        leadName = [vhECGTools leadName:i];
        [leadName drawInRect:rect withAttributes:standardAtt];
    }
    return;
}

+(CGMutablePathRef)build6x2ContinuncePath:(NSArray <NSArray <NSNumber *>*>*)ecgsArray fullLead:(ECGLead)extLead zeroX:(float)start_x pointPerPoint:(float)seekPerPoint zeroY:(float)start_y rateY:(float)y_rate lineSpace:(float)perlineSpace pix:(float)pixPermm{
    CGMutablePathRef path = CGPathCreateMutable();
    float currentX = 0.f;
    NSInteger indexFrom = 0;
    NSInteger indexLen = ecgsArray.firstObject.count/2;
    NSInteger indexTo = indexFrom + indexLen;
    for (int i=0;i<12;i++){
        float middle = start_y + (i%6 + 0.66f) * perlineSpace;
        currentX = start_x + (seekPerPoint * indexLen) * (i/6);
        NSArray *leadECGsArray = [ecgsArray objectAtIndex:i];
        
        //前3个导联有定标
        if (i < 6){
            CGPathMoveToPoint(path, NULL, currentX, middle);
            currentX += 1.5f * pixPermm;
            CGPathAddLineToPoint(path, NULL, currentX, middle);
            CGPathAddLineToPoint(path, NULL, currentX, middle - y_rate * pixPermm);
            currentX += 2.f * pixPermm;
            CGPathAddLineToPoint(path, NULL, currentX, middle - y_rate * pixPermm);
            CGPathAddLineToPoint(path, NULL, currentX, middle);
            currentX += 1.5f * pixPermm;
            CGPathAddLineToPoint(path, NULL, currentX, middle);
            CGPathMoveToPoint(path, NULL, -1.f, -1.f);
            CGPathCloseSubpath(path);
        }else{
            //后面的导联跳过定标宽度
            currentX += 5.f * pixPermm;
            //画小竖线
            CGPathMoveToPoint(path, NULL, currentX, middle);
            CGPathAddLineToPoint(path, NULL, currentX, middle - 10.f * pixPermm);
            CGPathMoveToPoint(path, NULL, -1.f, -1.f);
            CGPathCloseSubpath(path);
        }
        
        //ECG line start
        BOOL isPenDown = NO;
        indexFrom = indexLen * (i/6);
        indexTo = indexFrom + indexLen;
        for (NSInteger index = indexFrom;index<indexTo;index++){
            NSNumber *num = [leadECGsArray objectAtIndex:index];
            float y = middle - pixPermm * y_rate * [num floatValue]/1000.f;
            if (isPenDown){
                CGPathAddLineToPoint(path, NULL, currentX, y);
            }else{
                CGPathMoveToPoint(path, NULL, currentX, y);
                isPenDown = YES;
            }
            currentX += seekPerPoint;
        }
        CGPathMoveToPoint(path, NULL, -1.f, -1.f);
        CGPathCloseSubpath(path);
    }
    
    //draw ext lead
    float middle = start_y + 6.66f * perlineSpace;
    currentX = start_x;
    CGPathMoveToPoint(path, NULL, currentX, middle);
    currentX += 1.5f * pixPermm;
    CGPathAddLineToPoint(path, NULL, currentX, middle);
    CGPathAddLineToPoint(path, NULL, currentX, middle - y_rate * pixPermm);
    currentX += 2.f * pixPermm;
    CGPathAddLineToPoint(path, NULL, currentX, middle - y_rate * pixPermm);
    CGPathAddLineToPoint(path, NULL, currentX, middle);
    currentX += 1.5f * pixPermm;
    CGPathAddLineToPoint(path, NULL, currentX, middle);
    CGPathMoveToPoint(path, NULL, -1.f, -1.f);
    CGPathCloseSubpath(path);
    
    BOOL isPenDown = NO;
    for (NSNumber *num in [ecgsArray objectAtIndex:extLead]){
        float y = middle - pixPermm * y_rate * [num floatValue]/1000.f;
        if (isPenDown){
            CGPathAddLineToPoint(path, NULL, currentX, y);
        }else{
            CGPathMoveToPoint(path, NULL, currentX, y);
            isPenDown = YES;
        }
        currentX += seekPerPoint;
    }
    CGPathMoveToPoint(path, NULL, -1.f, -1.f);
    CGPathCloseSubpath(path);
    return path;
}

#pragma mark - LIMB
+(CGMutablePathRef)buildLIMBPath:(NSArray <NSArray <NSNumber *>*>*)ecgsArray zeroX:(float)start_x pointPerPoint:(float)seekPerPoint zeroY:(float)start_y rateY:(float)y_rate lineSpace:(float)perlineSpace pix:(float)pixPermm{
    NSArray *array = @[@YES,@YES,@YES,
                       @YES,@YES,@YES,
                       @NO,@NO,@NO,
                       @NO,@NO,@NO];
    return [vhECGPath buildCustomPath:ecgsArray zeroX:start_x pointPerPoint:seekPerPoint zeroY:start_y rateY:y_rate lineSpace:perlineSpace pix:pixPermm customLeads:array];
}

+(void)drawLIMBLeadName:(NSDictionary *)standardAtt startX:(float)start_x startY:(float)start_y lineSpace:(float)perlineSpace pixPermm:(float)pixPermm{
    NSArray *array = @[@YES,@YES,@YES,
                       @YES,@YES,@YES,
                       @NO,@NO,@NO,
                       @NO,@NO,@NO];
    [vhECGPath drawCustomLeadName:standardAtt startX:start_x startY:start_y lineSpace:perlineSpace pixPermm:pixPermm customLeads:array];
}


#pragma mark - Custom
+(CGMutablePathRef)buildCustomPath:(NSArray <NSArray <NSNumber *>*>*)ecgsArray zeroX:(float)start_x pointPerPoint:(float)seekPerPoint zeroY:(float)start_y rateY:(float)y_rate lineSpace:(float)perlineSpace pix:(float)pixPermm customLeads:(NSArray <NSNumber *>*)leadsArray{
    CGMutablePathRef path = CGPathCreateMutable();
    float middle = start_y + perlineSpace * 0.66f;
    for (int i=0;i<12;i++){
        if (NO == [[leadsArray objectAtIndex:i] boolValue]){
            //Jump no selected lead
            continue;
        }
        NSArray <NSNumber *>*leadECG = [ecgsArray objectAtIndex:i];
        float currentX = start_x;
        
        //画定标 begin
        if (0 == i%2 && (perlineSpace/pixPermm < (y_rate + 4.f))){
            //忽略定标
            currentX += 5.f * pixPermm;
        }else{
            CGPathMoveToPoint(path, NULL, currentX, middle);
            currentX += 1.5f * pixPermm;
            CGPathAddLineToPoint(path, NULL, currentX, middle);
            CGPathAddLineToPoint(path, NULL, currentX, middle - y_rate * pixPermm);
            currentX += 2.f * pixPermm;
            CGPathAddLineToPoint(path, NULL, currentX, middle - y_rate * pixPermm);
            CGPathAddLineToPoint(path, NULL, currentX, middle);
            currentX += 1.5f * pixPermm;
            CGPathAddLineToPoint(path, NULL, currentX, middle);
            CGPathMoveToPoint(path, NULL, -1.f, -1.f);
            CGPathCloseSubpath(path);
        }
        //定标结束
        
        BOOL isPenDown = NO;
        for (NSNumber *num in leadECG){
            float y = middle - pixPermm * y_rate * [num floatValue]/1000.f;
            if (isPenDown){
                CGPathAddLineToPoint(path, NULL, currentX, y);
            }else{
                CGPathMoveToPoint(path, NULL, currentX, y);
                isPenDown = YES;
            }
            currentX += seekPerPoint;
        }
        CGPathMoveToPoint(path, NULL, -1.f, -1.f);
        CGPathCloseSubpath(path);
        middle += perlineSpace;
    }
    return path;
}

+(void)drawCustomLeadName:(NSDictionary *)standardAtt startX:(float)start_x startY:(float)start_y lineSpace:(float)perlineSpace pixPermm:(float)pixPermm customLeads:(NSArray <NSNumber *>*)leadsArray{
    float middle = start_y + perlineSpace * 0.66f;
    for (int i=0;i<12;i++){
        if (NO == [[leadsArray objectAtIndex:i] boolValue]){
            continue;
        }
        CGRect rect = CGRectMake(start_x, middle + 0.f, 5.f * pixPermm, 40.f);
        NSString *leadName = [vhECGTools leadName:i];
        [leadName drawInRect:rect withAttributes:standardAtt];
        middle += perlineSpace;
    }
    return;
}


#pragma mark - Background Lines
+(CGMutablePathRef)buildBg_mmLinesIn:(CGRect)rect pix:(float)pixPermm{
    CGMutablePathRef path = CGPathCreateMutable();
    //画横线
    for (int i=0;i<1000000;i++){
        if (0 == i%5){
            continue;
        }
        float currentY = i * pixPermm + rect.origin.y;
        if (currentY > rect.origin.y + rect.size.height){
            break;
        }
        CGPathMoveToPoint(path, NULL, rect.origin.x,currentY);
        CGPathAddLineToPoint(path, NULL, rect.origin.x+rect.size.width, currentY);
        CGPathMoveToPoint(path, NULL, -1.f, -1.f);
        CGPathCloseSubpath(path);
    }
    
    //画竖线
    for (int i=0;i<100000;i++){
        if (0 == i%5){
            continue;
        }
        float currentX = i * pixPermm + rect.origin.x;
        if (currentX > rect.origin.x + rect.size.width){
            break;
        }
        CGPathMoveToPoint(path, NULL, currentX, rect.origin.y);
        CGPathAddLineToPoint(path, NULL, currentX, rect.origin.y + rect.size.height);
        CGPathMoveToPoint(path, NULL, -1.f, -1.f);
        CGPathCloseSubpath(path);
    }
    return path;
}

+(CGMutablePathRef)buildBg_5mmLinesIn:(CGRect)rect pix:(float)pixPermm{
    CGMutablePathRef path = CGPathCreateMutable();
    //画横线
    for (int i=0;i<1000000;i++){
        if (0 == i%5){
            if (0 == i%10){
                continue;
            }
            float currentY = i * pixPermm + rect.origin.y;
            if (currentY > rect.origin.y + rect.size.height){
                break;
            }
            CGPathMoveToPoint(path, NULL, rect.origin.x,currentY);
            CGPathAddLineToPoint(path, NULL, rect.origin.x+rect.size.width, currentY);
            CGPathMoveToPoint(path, NULL, -1.f, -1.f);
            CGPathCloseSubpath(path);
        }
    }
    
    //画竖线
    for (int i=0;i<100000;i++){
        if (0 == i%5){
            if (0 == i%10){
                continue;
            }
            float currentX = i * pixPermm + rect.origin.x;
            if (currentX > rect.origin.x + rect.size.width){
                break;
            }
            CGPathMoveToPoint(path, NULL, currentX, rect.origin.y);
            CGPathAddLineToPoint(path, NULL, currentX, rect.origin.y + rect.size.height);
            CGPathMoveToPoint(path, NULL, -1.f, -1.f);
            CGPathCloseSubpath(path);
        }
    }
    return path;
}

+(CGMutablePathRef)buildBg_10mmLinesIn:(CGRect)rect pix:(float)pixPermm{
    CGMutablePathRef path = CGPathCreateMutable();
    //画横线
    for (int i=0;i<1000000;i++){
        if (0 == i%10){
            float currentY = i * pixPermm + rect.origin.y;
            if (currentY > rect.origin.y + rect.size.height){
                break;
            }
            CGPathMoveToPoint(path, NULL, rect.origin.x,currentY);
            CGPathAddLineToPoint(path, NULL, rect.origin.x+rect.size.width, currentY);
            CGPathMoveToPoint(path, NULL, -1.f, -1.f);
            CGPathCloseSubpath(path);
        }
    }
    
    //画竖线
    for (int i=0;i<100000;i++){
        if (0 == i%10){
            float currentX = i * pixPermm + rect.origin.x;
            if (currentX > rect.origin.x + rect.size.width){
                break;
            }
            CGPathMoveToPoint(path, NULL, currentX, rect.origin.y);
            CGPathAddLineToPoint(path, NULL, currentX, rect.origin.y + rect.size.height);
            CGPathMoveToPoint(path, NULL, -1.f, -1.f);
            CGPathCloseSubpath(path);
        }
    }
    return path;
}


#pragma mark - Single ECG Line
+(CGMutablePathRef)buildOneLineECG:(NSArray <NSNumber *>*)ecgsArray zeroX:(float)start_x pointPerPoint:(float)seekPerPoint middleY:(float)middle rateY:(float)y_rate pix:(float)pixPermm{
    CGMutablePathRef path = CGPathCreateMutable();
    float x = start_x;
    BOOL ispenDown = NO;
    for (NSNumber *num in ecgsArray){
        float y = middle - pixPermm * y_rate * [num floatValue]/1000.f;
        if (ispenDown){
            CGPathAddLineToPoint(path, NULL, x, y);
        }else{
            CGPathMoveToPoint(path, NULL, x, y);
            ispenDown = YES;
        }
        x += seekPerPoint;
    }
    CGPathMoveToPoint(path, NULL, -1.f, -1.f);
    CGPathCloseSubpath(path);
    return path;
}
@end
